//
//  GradientView.swift
//  WearDu
//
//  Created by wang tiao on 2025/6/3.
//

import UIKit


class GradientView: UIView {
    
    var colors: [UIColor]? {
        didSet { updateColors() }
    }
    var locations: [NSNumber]? {
        didSet { gradientLayer.locations = locations }
    }
    var isGradientBorder: Bool = false {
        didSet { updateBorderMask() }
    }
    var borderWidth: CGFloat = 2.0 {
        didSet { updateBorderMask() }
    }
    var cornerRadius: CGFloat = 8.0 {
        didSet { updateBorderMask() }
    }
    
    private let gradientLayer = CAGradientLayer()
    private let borderMask = CAShapeLayer()
    
    override init(frame: CGRect) {
        super.init(frame: frame)
        setupDefault()
    }
    
    required init?(coder: NSCoder) {
        super.init(coder: coder)
        setupDefault()
    }
    
    override func layoutSubviews() {
        super.layoutSubviews()
        gradientLayer.frame = bounds
        updateBorderMask()
    }
    
    private func setupDefault() {
        backgroundColor = .clear
        
        gradientLayer.startPoint = CGPoint(x: 0, y: 0)
        gradientLayer.endPoint = CGPoint(x: 0, y: 1)
        layer.addSublayer(gradientLayer)
        
        colors = [UIColor.white.withAlphaComponent(0), .red]
        updateColors()
    }
    
    private func updateColors() {
        gradientLayer.colors = colors?.map { $0.cgColor }
    }
    
    private func updateBorderMask() {
        guard isGradientBorder else {
            gradientLayer.mask = nil
            return
        }
        let path = UIBezierPath(
            roundedRect: bounds.insetBy(dx: borderWidth / 2, dy: borderWidth / 2),
            cornerRadius: cornerRadius
        )
        borderMask.path = path.cgPath
        borderMask.fillColor = UIColor.clear.cgColor
        borderMask.strokeColor = UIColor.black.cgColor
        borderMask.lineWidth = borderWidth
        gradientLayer.mask = borderMask
    }
    
    func setStartPoint(_ startPoint: CGPoint, endPoint: CGPoint) {
        gradientLayer.startPoint = startPoint
        gradientLayer.endPoint = endPoint
    }
}

class GradientButton: UIButton {
    
    var colors: [UIColor]? {
        didSet { updateColors() }
    }
    var locations: [NSNumber]? {
        didSet { gradientLayer.locations = locations }
    }
    var isGradientBorder: Bool = false {
        didSet { updateBorderMask() }
    }
    var borderWidth: CGFloat = 2.0 {
        didSet { updateBorderMask() }
    }
    var cornerRadius: CGFloat = 8.0 {
        didSet { updateBorderMask() }
    }
    
    private let gradientLayer = CAGradientLayer()
    private let borderMask = CAShapeLayer()
    
    override init(frame: CGRect) {
        super.init(frame: frame)
        setupDefault()
    }
    
    required init?(coder: NSCoder) {
        super.init(coder: coder)
        setupDefault()
    }
    
    override func layoutSubviews() {
        super.layoutSubviews()
        gradientLayer.frame = bounds
        updateBorderMask()
    }
    
    private func setupDefault() {
        backgroundColor = .clear
        
        gradientLayer.startPoint = CGPoint(x: 0, y: 0)
        gradientLayer.endPoint = CGPoint(x: 0, y: 1)
        layer.addSublayer(gradientLayer)
        
        colors = [UIColor.white.withAlphaComponent(0), .red]
        updateColors()
    }
    
    private func updateColors() {
        gradientLayer.colors = colors?.map { $0.cgColor }
    }
    
    private func updateBorderMask() {
        guard isGradientBorder else {
            gradientLayer.mask = nil
            return
        }
        let path = UIBezierPath(
            roundedRect: bounds.insetBy(dx: borderWidth / 2, dy: borderWidth / 2),
            cornerRadius: cornerRadius
        )
        borderMask.path = path.cgPath
        borderMask.fillColor = UIColor.clear.cgColor
        borderMask.strokeColor = UIColor.black.cgColor
        borderMask.lineWidth = borderWidth
        gradientLayer.mask = borderMask
    }
    
    func setStartPoint(_ startPoint: CGPoint, endPoint: CGPoint) {
        gradientLayer.startPoint = startPoint
        gradientLayer.endPoint = endPoint
    }
}
